package com.springboot.chongwu.service.impl;

import cn.dev33.satoken.stp.StpUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.springboot.chongwu.comm.DictionaryEnum;
import com.springboot.chongwu.comm.ResultEnum;
import com.springboot.chongwu.entity.SysManager;
import com.springboot.chongwu.entity.SysMenu;
import com.springboot.chongwu.entity.SysRole;
import com.springboot.chongwu.entity.req.SysRoleReq;
import com.springboot.chongwu.entity.search.SysRoleSearch;
import com.springboot.chongwu.exception.MyException;
import com.springboot.chongwu.mapper.SysRoleMapper;
import com.springboot.chongwu.qpage.QPage;
import com.springboot.chongwu.service.ISysManagerService;
import com.springboot.chongwu.service.ISysMenuService;
import com.springboot.chongwu.service.ISysRoleMenuService;
import com.springboot.chongwu.service.ISysRoleService;
import com.springboot.chongwu.util.*;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.*;

/**
 * <p>
 * 角色表 服务实现类
 * </p>
 *
 * @author astupidcoder
 * @since 2021-06-15
 */
@Service
public class SysRoleServiceImpl extends ServiceImpl<SysRoleMapper, SysRole> implements ISysRoleService {

    @Autowired
    private ISysMenuService iHjMenuService;
    @Autowired
    private ISysRoleMenuService iHjRoleMenuService;

    @Autowired
    private ISysManagerService iSysManagerService;

    /**
     * 获取角色列表
     * @return
     */
    @Override
    public IPage<SysRole> getListAll(QPage qPage, SysRoleSearch hjRoleSearch) {
        QueryWrapper<SysRole> queryWrapper=new QueryWrapper<>();
        queryWrapper.lambda().like(StringUtils.isNotEmpty(hjRoleSearch.getRoleName()),SysRole::getRoleName,hjRoleSearch.getRoleName());
        queryWrapper.eq("is_del", DictionaryEnum.IS_DEL_N.getCode());
        queryWrapper.orderByDesc("ctime");
        IPage<SysRole> hjRoleList=this.page(new Page<>(qPage.getOffset(), qPage.getLimit()),queryWrapper);
        return hjRoleList;
    }

    /**
     * 新增角色
     * @param hjRoleReq
     * @return
     */
    @Transactional
    @Override
    public ResultView addRole(SysRoleReq hjRoleReq) {
        SysRole hjRole=new SysRole();
        BeanUtils.copyProperties(hjRoleReq,hjRole);
        hjRole.setRoleId(IdentityUtil.identityId("RO"));
        hjRole.setCtime(new Date());
        hjRole.setIsDel(DictionaryEnum.IS_DEL_N.getCode());
        boolean count=this.save(hjRole);
        if(!count){
            throw new MyException(ResultEnum.CODE_2,"添加角色出现异常");
        }
        //新增权限角色关联表
        boolean isOk=this.iHjRoleMenuService.saveRoleMenu(hjRoleReq.getMenuId(),hjRole.getRoleId());
        if(!isOk){
            throw new MyException(ResultEnum.CODE_2,"添加角色权限关联出现异常");
        }
        return ResultView.ok();
    }

    /**
     * 更新角色
     * @param hjRoleReq
     * @return
     */
    @Transactional
    @Override
    public ResultView updateRole(SysRoleReq hjRoleReq) {
        SysRole hjRole=new SysRole();
        BeanUtils.copyProperties(hjRoleReq,hjRole);
        hjRole.setUtime(new Date());
        boolean count=this.updateById(hjRole);
        if(!count){
            throw new MyException(ResultEnum.CODE_2,"修改角色出现异常");
        }
        //删除之前关联这个角色的菜单角色数据
        this.iHjRoleMenuService.removeMenuRoleId(hjRoleReq.getRoleId());
        //新增权限角色关联表
        boolean isOk=this.iHjRoleMenuService.saveRoleMenu(hjRoleReq.getMenuId(),hjRole.getRoleId());
        if(!isOk){
            throw new MyException(ResultEnum.CODE_2,"添加角色权限关联出现异常");
        }
        return ResultView.ok();
    }

    /**
     * 获取当前角色菜单
     * @param roleId
     * @return
     */
    @Override
    public ResultView roleMenuList(String roleId) {
        Map<String,Object> map=new HashMap<>();
        List<Tree<SysMenu>> trees = new ArrayList<Tree<SysMenu>>();
        //获取所有菜单集合
        List<SysMenu> menuList=this.iHjMenuService.getListAll(null);
        //当前角色绑定的菜单
        if(StringUtils.isNotBlank(roleId)){
            List<Object> roleMenus=iHjRoleMenuService.getByRoleId(roleId);
            map.put("menuId",roleMenus);
        }
        for (SysMenu sysMenuDO : menuList) {
            Tree<SysMenu> tree = new Tree<SysMenu>();
            tree.setId(sysMenuDO.getMenuId());
            tree.setParentId(sysMenuDO.getParentId());
            tree.setText(sysMenuDO.getMenuName());
            tree.setPrem(sysMenuDO.getMenuPerm());
            tree.setMenuUrl(sysMenuDO.getMenuUrl());
            trees.add(tree);
        }
        // 默认顶级菜单为０，根据数据库实际情况调整
        List<Tree<SysMenu>> list = BuildTree.buildList(trees, "");
        map.put("menu",list);
        return ResultView.ok(map);
    }

    /**
     * 删除角色
     * @param roleId 角色ID
     * @return
     */
    @Transactional
    @Override
    public ResultView deleteRole(String roleId) {
        SysRole hjRole=new SysRole();
        hjRole.setRoleId(roleId);
        hjRole.setUtime(new Date());
        hjRole.setIsDel(DictionaryEnum.IS_DEL_Y.getCode());
        boolean isOk=this.updateById(hjRole);
        if(!isOk){
            throw new MyException(ResultEnum.CODE_2,"删除角色出现异常");
        }
        return ResultView.ok();
    }

    /**
     * 批量删除角色
     * @param roleId
     * @return
     */
    @Transactional
    @Override
    public ResultView batchDeleteRole(String[] roleId) {
        List<SysRole> hjRoleList=new ArrayList<>();
        for (String role : roleId) {
            SysRole hjRole=new SysRole();
            hjRole.setRoleId(role);
            hjRole.setIsDel(DictionaryEnum.IS_DEL_Y.getCode());
            hjRoleList.add(hjRole);
        }
        boolean isOk=this.updateBatchById(hjRoleList);
        if(!isOk){
            throw new MyException(ResultEnum.CODE_2,"批量删除角色出现异常");
        }
        return ResultView.ok();
    }

    /**
     * 根据角色ID获取当前数据
     * @param roleId
     * @return
     */
    @Override
    public ResultView getRoleId(String roleId) {
        SysRole hjRole=this.getById(roleId);
        return ResultView.ok(hjRole);
    }

    /**
     * 获取角色列表(不分页)
     * @return
     */
    @Override
    public List<SysRole> getListAll() {
        QueryWrapper<SysRole> queryWrapper=new QueryWrapper<>();
        queryWrapper.eq("is_del", DictionaryEnum.IS_DEL_N.getCode());
        SysManager sysManager=this.iSysManagerService.getById(StpUtil.getLoginIdAsString());
        if(sysManager.getMType()!=1){
            queryWrapper.eq("role_name", "员工");
        }
        queryWrapper.orderByDesc("ctime");
        List<SysRole> hjRoleList=this.list(queryWrapper);
        return hjRoleList;
    }

}
